//
//  recordManager.m
//  tcpoctest
//
//  Created by gump on 11/26/12.
//  Copyright (c) 2012 gump. All rights reserved.
//

#import "recordManager.h"
#import "SpeexCodec.h"
#import "LocalPathDataSource.h"

@implementation recordManager

static recordManager *sharedInstance = nil;

+(recordManager*)shareControl
{
    if(!sharedInstance)
    {
        sharedInstance = [[super alloc] init];
    }
    return sharedInstance;
}

-(void)startRecord
{
    AVAudioSession *session = [AVAudioSession sharedInstance];
    NSError *sessionError;
    
    [session setCategory:AVAudioSessionCategoryPlayAndRecord error:&sessionError];
    
    if(session == nil)
    {
        AS_LOG(@"Error creating session: %@", [sessionError description]);
    }
    else
        [session setActive:YES error:nil];

    
    [self startAudioR];
}

-(void)startAudioR
{
    lowPassResults = 0;
    
    self.recordedFile = [NSURL fileURLWithPath:[[[DataControl shareControl].localpathds LPChatPath]
                                                stringByAppendingPathComponent:
                                                getFileNameWithDate(FT_CHAT)]];
    
    NSMutableDictionary *recordSetting = [[NSMutableDictionary alloc] init];
    [recordSetting setValue:[NSNumber numberWithInt:kAudioFormatLinearPCM] forKey:AVFormatIDKey];
    [recordSetting setValue:[NSNumber numberWithInt:8000] forKey:AVSampleRateKey];
    [recordSetting setValue:[NSNumber numberWithInt:1] forKey:AVNumberOfChannelsKey];
    [recordSetting setValue:[NSNumber numberWithInt:16] forKey:AVLinearPCMBitDepthKey];
    
    NSError *error;
    recorder = [[AVAudioRecorder alloc] initWithURL:self.recordedFile settings:recordSetting error:&error];
    
    if (recorder) {
		[recorder prepareToRecord];
		recorder.meteringEnabled = YES;
		[recorder record];
        
        startRecordTime = recorder.currentTime;
	} else{
		AS_LOG(@"%@",[error description]);
    }
    
    recordstate = RS_START;
    recordTimer = 0;
}

-(void)stopRecord
{
    [self stopAudioR];
    
    NSData *PCMData = [NSData dataWithContentsOfURL:self.recordedFile];
    
    NSData *SpeexData = EncodeWAVEToSpeex(PCMData, 1, 16);
    [SpeexData writeToURL:self.recordedFile atomically:YES];
}

-(void)stopAudioR
{
    recordstate = RS_NULL;
    
    startRecordTime = recorder.currentTime - startRecordTime;
    
    [recorder stop];
    
    AS_LOG(@"record length is %f",startRecordTime);
    
    recorder = nil;
}

-(double)updateRecordPower
{
 [recorder updateMeters];
  const double ALPHA = 0.05;
  double peakPowerForChannel = pow(10, (0.05 * [recorder peakPowerForChannel:0]));
  lowPassResults = ALPHA * peakPowerForChannel + (1.0 - ALPHA) * lowPassResults;
  return lowPassResults;
}

-(id)init
{
    self = [super init];
    if(self)
    {
        UInt32 sessionCategory = kAudioSessionCategory_MediaPlayback;
             AudioSessionSetProperty(kAudioSessionProperty_AudioCategory,
                                                                   sizeof(sessionCategory),
                                                                   &sessionCategory);
        
             UInt32 audioRouteOverride = kAudioSessionOverrideAudioRoute_Speaker;
             AudioSessionSetProperty (kAudioSessionProperty_OverrideAudioRoute,
                                                                     sizeof (audioRouteOverride),
                                                                      &audioRouteOverride);
        AVAudioSession *session = [AVAudioSession sharedInstance];
         NSError *sessionError;
        [session setCategory:AVAudioSessionCategoryPlayback error:&sessionError];
       
        [session setCategory:AVAudioSessionCategoryPlayAndRecord error:&sessionError];
        
        if(session == nil)
        {
            AS_LOG(@"Error creating session: %@", [sessionError description]);
        }
        else
            [session setActive:YES error:nil];
        
        recordTimer = 0;
        recordstate = RS_NULL;
        startRecordTime = 0.0f;
    }
    return self;
}

-(void)tick
{
    switch (recordstate) {
        case RS_START:
            if(recordTimer > 0)
            {
                recordstate = RS_BEGIN;
                recordstate = 0;
            }
            else
            {
                ++recordTimer;
            }
            break;
            
        default:
            break;
    }
}

-(double)GetRecordLength
{
    return startRecordTime;
}

@end
